import os
from datetime import datetime

import ujson
from flask import send_from_directory, render_template
from flask_cors import cross_origin
from werkzeug.exceptions import abort

from crawleth.config import API_DAILY_EXPORT_DIRECTORY, API_HOURLY_EXPORT_DIRECTORY, API_DIRECTORY
from flaskapp import app


@app.route('/')
def home():
    return render_template("pages/index.html")


@app.route('/api')
def api_home():
    return render_template("pages/api.html")


@app.route('/api/latest/raw')
@cross_origin()
def last_raw():
    return send_from_directory(app.static_folder, API_HOURLY_EXPORT_DIRECTORY + 'latest/raw_aggregated_results.json')


@app.route('/api/latest/deviant/<string:category>')
@cross_origin()
def last_deviant(category: str):
    if category not in ('aliases', 'subnets', 'groups', 'all'):
        abort(404)
    if category == 'aliases':
        return send_from_directory(app.static_folder, API_HOURLY_EXPORT_DIRECTORY + 'latest/aliases.json')
    if category == 'groups':
        return send_from_directory(app.static_folder, API_HOURLY_EXPORT_DIRECTORY + 'latest/groups.json')
    if category == 'subnets':
        return send_from_directory(app.static_folder, API_HOURLY_EXPORT_DIRECTORY + 'latest/subnets.json')
    with open(API_HOURLY_EXPORT_DIRECTORY + 'latest/aliases.json', 'r') as aliases:
        with open(API_HOURLY_EXPORT_DIRECTORY + 'latest/groups.json', 'r') as groups:
            with open(API_HOURLY_EXPORT_DIRECTORY + 'latest/subnets.json', 'r') as subnets:
                out = {"aliases": ujson.load(aliases), "groups": ujson.load(groups), "subnets": ujson.load(subnets)}
    return out


@app.route('/api/<int:year>/<int:month>/<int:day>/deviant/<string:category>')
@cross_origin()
def this_deviant(year: int, month: int, day: int, category: str):
    if year > datetime.utcnow().year or month > 12 or day > 31 or year < 2021 or month < 1 or day < 1:
        abort(422)
    if category not in ('aliases', 'subnets', 'groups', 'all'):
        abort(404)
    requested_path = f"{day:02d}_{month:02d}_{year:04d}/"
    if not os.path.isdir(app.static_folder + "/" + API_DAILY_EXPORT_DIRECTORY + requested_path):
        abort(404)
    if category == 'aliases':
        return send_from_directory(app.static_folder, f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}aliases.json')
    if category == 'groups':
        return send_from_directory(app.static_folder, f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}groups.json')
    if category == 'subnets':
        return send_from_directory(app.static_folder, f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}subnets.json')
    with open(f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}aliases.json', 'r') as aliases:
        with open(f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}groups.json', 'r') as groups:
            with open(f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}subnets.json', 'r') as subnets:
                out = {"aliases": ujson.load(aliases), "groups": ujson.load(groups), "subnets": ujson.load(subnets)}
    return out


@app.route('/api/<int:year>/<int:month>/<int:day>/raw')
@cross_origin()
def this_raw(year: int, month: int, day: int):
    if year > datetime.utcnow().year or month > 12 or day > 31 or year < 2021 or month < 1 or day < 1:
        abort(422)
    requested_path = f"{day:02d}_{month:02d}_{year:04d}/"
    if not not os.path.isdir(app.static_folder + requested_path):
        abort(404)
    return send_from_directory(app.static_folder,
                               f'{API_DAILY_EXPORT_DIRECTORY}{requested_path}raw_aggregated_results.json')


@app.route('/api/history')
@cross_origin()
def stats():
    return send_from_directory(app.static_folder, API_DIRECTORY + 'stats.json')
